package com.example.simple_android.annotation.impl;

import android.text.TextUtils;

import com.example.simple_android.Manager.impl.InjectionManager;
import com.example.simple_android.annotation.InjectionMark;
import com.example.simple_android.utils.ReflectionsUtil;

import java.lang.reflect.Constructor;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Set;

public class InjectionMarkImpl {

    /**
     * 扫描全局，将被InjectionMark注解标记的对象，全部实例化并且存放到InjectionManager对象中管理
     */
    public static void injectionMarkClass() {
        Set<Class<?>> classByAnnotationClass = ReflectionsUtil.getClassByAnnotationClass(InjectionMark.class);
        if (classByAnnotationClass == null){
            return;
        }
        for (Class<?> cls : classByAnnotationClass) {
            InjectionMark injectionMark = cls.getDeclaredAnnotation(InjectionMark.class);
            if (injectionMark == null) {
                continue;
            }
            String staticMethod = injectionMark.staticMethod();
            String flag = injectionMark.flag();
            try {
                if (TextUtils.isEmpty(staticMethod)) {
                    Constructor<?>[] declaredConstructors = cls.getDeclaredConstructors();
                    for (Constructor<?> constructor : declaredConstructors) {
                        if (constructor.getParameterCount() != 0) {
                            continue;
                        }
                        Object o = constructor.newInstance();
                        // 注入管理者
                        InjectionManager injectionManager = InjectionManager.getInstance();
                        if (TextUtils.isEmpty(flag)) {
                            injectionManager.register(cls.getName(), o);
                        } else {
                            injectionManager.register(cls.getName().concat(".").concat(flag), o);
                        }
                    }
                } else {
                    Method method = cls.getDeclaredMethod(staticMethod);
                    method.setAccessible(true);
                    Object o = method.invoke(null);
                    // 注入管理者
                    InjectionManager injectionManager = InjectionManager.getInstance();
                    if (TextUtils.isEmpty(flag)) {
                        injectionManager.register(cls.getName(), o);
                    } else {
                        injectionManager.register(cls.getName().concat(".").concat(flag), o);
                    }
                }
            } catch
            (IllegalAccessException | InstantiationException | InvocationTargetException | NoSuchMethodException e) {
                e.printStackTrace();
            }
        }
    }

    /**
     * 将指定对象存放到InjectionManager中管理
     *
     * @param key 和被管理者绑定的键
     * @param o   被管理者
     */
    public static void injectionMarkClass(String key, Object o) {
        InjectionManager.getInstance().register(key, o);
    }

    /**
     * 将指定对象存放到InjectionManager中管理
     *
     * @param o 被管理的对象
     */
    public static void injectionMarkClass(Object o) {
        injectionMarkClass(o.getClass().getName(), o);
    }
}
